﻿using System;
using System.Collections;
using UnityEngine;

public class HashtableEx :IEnumerable
{
	protected Hashtable _data = new Hashtable();

	public HashtableEx( Hashtable data=null )
	{
        if (data == null) return;
		this._data = data;
	}

	public HashtableEx( HashtableEx data )
	{
		this._data = data.GetData();
	}

	public IEnumerator GetEnumerator()
	{
		return this._data.GetEnumerator();
	}

	public virtual Hashtable GetData()
	{
		return this._data;
	}

	public virtual void SetData( Hashtable data )
	{
		if ( data == null )
			throw new ArgumentNullException();

		this._data = data;
	}

	public virtual int GetCount()
	{
		return this._data.Count;
	}

	public virtual bool Contains( object key )
	{
		return this._data.Contains( key );
	}

	public virtual bool ContainsKey( object key )
	{
		return this._data.ContainsKey( key );
	}

	public virtual bool ContainsValue( object value )
	{
		return this._data.ContainsValue( value );
	}

	/// <summary>
	/// 定义索引器
	/// </summary>
	/// <param name="key">键</param>
	/// <returns>值</returns>
	public virtual object this[object key]
	{
		get
		{
			return this._data[key];
		}
		set
		{
			this._data[key] = value;
		}
	}

	public virtual void Add( object key, object value )
	{
		this._data.Add( key, value );
	}
    public virtual void AddData(Hashtable data)
    {
        foreach(DictionaryEntry d in data){
            _data[d.Key] = d.Value;
        }
    }
	public virtual void Remove( object key )
	{
		this._data.Remove( key );
	}

	public virtual void Clear()
	{
		this._data.Clear();
	}

	#region Gets
	public bool GetBoolean( string key )
	{
		return Convert.ToBoolean( this[key] );
	}

	public byte GetByte( string key )
	{
		return Convert.ToByte( this[key] );
	}

	public char GetChar( string key )
	{
		return Convert.ToChar( this[key] );
	}

	public int GetInt( string key )
	{
		return Convert.ToInt32( this[key] );
	}

	public ushort GetShort( string key )
	{
		return Convert.ToUInt16( this[key] );
	}

	public long GetLong( string key )
	{
		return Convert.ToInt64( this[key] );
	}

	public double GetDouble( string key )
	{
		return Convert.ToDouble( this[key] );
	}

	public float GetFloat( string key )
	{
		return Convert.ToSingle( this[key] );
	}

	public string GetString( string key )
	{
		return Convert.ToString( this[key] );
	}

	public DateTime GetDate( string key )
	{
		return Convert.ToDateTime( this[key] );
	}

	public ArrayList GetList( string key )
	{
		if (this [key] == null) {
			return ( ArrayList )this[key];
		}
		if ((this [key]).GetType () != typeof(ArrayList)) {
			return null;
		}
		return ( ArrayList )this[key];
	}

	public Hashtable GetMap( string key )
	{
		return ( Hashtable )this[key];
	}
    public HashtableEx GetMapEx(string key)
    {
        return new HashtableEx((Hashtable)this[key]);
    }
    public bool[] GetBooleans( string key )
	{
		return ( bool[] )this[key];
	}

	public byte[] GetBytes( string key )
	{
		return ( byte[] )this[key];
	}

	public ushort[] GetShorts( string key )
	{
		return ( ushort[] )this[key];
	}

	public int[] GetInts( string key )
	{
		return ( int[] )this[key];
	}

	public long[] GetLongs( string key )
	{
		return ( long[] )this[key];
	}

	public double[] GetDoubles( string key )
	{
		return ( double[] )this[key];
	}

	public string[] GetStrings( string key )
	{
		return ( string[] )this[key];
	}

	public bool[] GetBooleans2( string key )
	{
		ArrayList list = ( ArrayList )this[key];
		return list.ToArray( typeof( bool ) ) as bool[];
	}

	public byte[] GetBytes2( string key )
	{
		ArrayList list = ( ArrayList )this[key];
		return list.ToArray( typeof( byte ) ) as byte[];
	}

	public ushort[] GetShorts2( string key )
	{
		ArrayList list = ( ArrayList )this[key];
		return list.ToArray( typeof( ushort ) ) as ushort[];
	}

	public int[] GetInts2( string key )
	{
		ArrayList list = ( ArrayList )this[key];
		int[] arr = new int[list.Count];
		for (int i = 0; i < list.Count; ++i) {
			arr[i] = Convert.ToInt32(list[i]);
		}
		return arr;
	}

	public long[] GetLongs2( string key )
	{
		ArrayList list = ( ArrayList )this[key];
		return list.ToArray( typeof( long ) ) as long[];
	}

	public double[] GetDoubles2( string key )
	{
		ArrayList list = ( ArrayList )this[key];
		return list.ToArray( typeof( double ) ) as double[];
	}

	public string[] GetStrings2( string key )
	{
		ArrayList list = ( ArrayList )this[key];
		return list.ToArray( typeof( string ) ) as string[];
	}

	public ArrayList[] GetLists( string key )
	{
		return ( ArrayList[] )this[key];
	}

	public Hashtable[] GetMaps( string key )
	{
		return ( Hashtable[] )this[key];
	}

	public object[] GetObjects( string key )
	{
		return ( object[] )this[key];
	}

	public Vector2 GetVector2( string key )
	{
		string str = ( string )this[key];
		if ( !string.IsNullOrEmpty( str ) )
		{
			string[] strs = str.Split( ',' );
			if ( strs.Length < 2 )
				return Vector2.zero;
			return new Vector2( Convert.ToSingle( strs[0] ), Convert.ToSingle( strs[1] ) );
		}
		return Vector2.zero;
	}

	public Vector3 GetVector3( string key )
	{
		string str = ( string )this[key];
		if ( !string.IsNullOrEmpty( str ) )
		{
			string[] strs = str.Split( ',' );
			if ( strs.Length < 3 )
				return Vector3.zero;
			return new Vector3( Convert.ToSingle( strs[0] ), Convert.ToSingle( strs[1] ), Convert.ToSingle( strs[2] ) );
		}
		return Vector3.zero;
	}

	public Vector4 GetVector4( string key )
	{
		string str = ( string )this[key];
		if ( !string.IsNullOrEmpty( str ) )
		{
			string[] strs = str.Split( ',' );
			if ( strs.Length < 4 )
				return Vector4.zero;
			return new Vector4( Convert.ToSingle( strs[0] ), Convert.ToSingle( strs[1] ), Convert.ToSingle( strs[2] ), Convert.ToSingle( strs[3] ) );
		}
		return Vector4.zero;
	}

	public void SetVector2( string key, Vector2 v )
	{
		this[key] = string.Format( "{0},{1}", v.x, v.y );
	}

	public void SetVector3( string key, Vector3 v )
	{
		this[key] = string.Format( "{0},{1},{2}", v.x, v.y, v.z );
	}

	public void SetVector4( string key, Vector4 v )
	{
		this[key] = string.Format( "{0},{1}.{2},{3}", v.x, v.y, v.z, v.w );
	}

	public T GetType<T>( string key )
	{
		return ( T )this[key];
	}

	public string[] keys
	{
		get
		{
			string[] rKeys = new string[this._data.Keys.Count];
			this._data.Keys.CopyTo( rKeys, 0 );
			return rKeys;
		}
	}
	#endregion

}
